package br.com.fidalgotecnologia.core.data.abs;

import java.util.List;

import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.persistence.EntityManager;
import javax.transaction.HeuristicMixedException;
import javax.transaction.HeuristicRollbackException;
import javax.transaction.NotSupportedException;
import javax.transaction.RollbackException;
import javax.transaction.SystemException;
import javax.transaction.UserTransaction;

import org.hibernate.Criteria;
import org.hibernate.Session;

import br.com.fidalgotecnologia.core.data.impl.DAOimpl;



public abstract class BaseDAO<T> implements DAOimpl<T>{
	private Context contexto;
	private UserTransaction userTransaction;
	
	public BaseDAO() {
		try {
			contexto = new InitialContext();
		} catch (NamingException e) {
			e.printStackTrace();
		}
	}
	public boolean inserir(T  entidade){
		boolean retorno = false;
		try {
			beginUserTransaction();
		
		EntityManager em = getEntityManager();
	    Session session = (Session)em.getDelegate();
	    session.beginTransaction();
	   session.saveOrUpdate(entidade);
	    session.getTransaction().commit();
	    commitUserTransaction();
	    retorno = true;
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	   return retorno;
	}
	
	public void deletar(T  entidade){
		try {
			beginUserTransaction();
		
		EntityManager em = getEntityManager();
	    Session session = (Session)em.getDelegate();
	    session.beginTransaction();
	    session.delete(entidade);
	    session.getTransaction().commit();
	    commitUserTransaction();
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	public List<T> listar(){
		List<T> retorno = null;
		try {
			beginUserTransaction();
		
		EntityManager em = getEntityManager();
	    Session session = (Session)em.getDelegate();
	    session.beginTransaction();
	    Criteria criteria = session.createCriteria(getClasse());
	    criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);
	    retorno = criteria.list();
	    session.getTransaction().commit();
	    commitUserTransaction();
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	    return retorno;
	}
	
	public void beginUserTransaction() throws Exception{
		
			userTransaction = (UserTransaction) contexto.lookup("java:comp/UserTransaction");
			userTransaction.begin();
		
	}

	public EntityManager getEntityManager(){
		EntityManager em = null;
	    try {
			em = (EntityManager) contexto.lookup("java:/layarServiceEM");
		} catch (NamingException e) {
			e.printStackTrace();
		}
		return em;
	}
	
	public void commitUserTransaction() throws SecurityException, IllegalStateException, RollbackException, HeuristicMixedException, HeuristicRollbackException, SystemException{
		
			userTransaction.commit();
		
	}


}
